﻿using mozhi.smarterp.Finance.Basedatas.Repository;
using mozhi.smarterp.Finance.Enums;
using mozhi.smarterp.Finance.Files.Repository;
using mozhi.smarterp.Finance.Querys;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Volo.Abp;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Guids;

namespace mozhi.smarterp.Finance.Basedatas
{
    public class PrintTemplateAppService : FinanceAppService, IPrintTemplateAppService
    {
        private IPrintTemplateRepository _templateRepository;
        private IGuidGenerator _guidGenerator;
        private IFileRepository _fileRepository;
        public PrintTemplateAppService(IPrintTemplateRepository templateRepository, IGuidGenerator guidGenerator ,IFileRepository fileRepository ,IServiceProvider serviceProvider)
            : base(serviceProvider)
        {
            _templateRepository = templateRepository;
            _guidGenerator = guidGenerator;
            _fileRepository = fileRepository;
        }

        public async Task<PagedResultDto<PrintTemplateDto>> FindAsync(PrintTemplatePageQuery query)
        {
            var templates = await _templateRepository.FindAsync(query);

            var count = await _templateRepository.GetCountAsync(query);

            var result = new PagedResultDto<PrintTemplateDto>();
            
            var items  = ObjectMapper.Map<List<PrintTemplate>, List<PrintTemplateDto>>(templates);

            await LoadFileInfoAsync(items);

            result.TotalCount = count;
            result.Items = items;

            return result;
        }

        public async Task<PrintTemplateDto> GetAsync(Guid id)
        {
            var template = await _templateRepository.FindAsync(id);

            if (template == null)
                throw new UserFriendlyException($"模板：{id}不存在已存在", "100000");

            var result = ObjectMapper.Map<PrintTemplate, PrintTemplateDto>(template);

            await _operationLogManager.LogAsync(ModuleCodeType.PrintTemplate, Enums.OperationType.Add, template, null);

            await LoadFileInfoAsync(new List<PrintTemplateDto>() { result });

            return result;
        }

        public async Task<PrintTemplateDto> CreateAsync(PrintTemplateCreateDto dto)
        {
            var matchCount = await _templateRepository.GetCountAsync(new PrintTemplatePageQuery() { PageIndex = 1, PageSize = 1, Name = dto.Name });

            if (matchCount > 0)
                throw new UserFriendlyException($"模板名称：{dto.Name}已存在", "100000");


            var template = new PrintTemplate(_guidGenerator.Create(), dto.Name, dto.ModuleCode, dto.TemplateFileId, dto.ImageFileId);

            template = await _templateRepository.InsertAsync(template);

            var result = ObjectMapper.Map<PrintTemplate, PrintTemplateDto>(template);

            await LoadFileInfoAsync(new List<PrintTemplateDto>() { result });

            await _operationLogManager.LogAsync(ModuleCodeType.PrintTemplate, Enums.OperationType.Add, template, null);

            return result;
        }

        public async Task<PrintTemplateDto> UpdateAsync(PrintTemplateUpdateDto dto)
        {
            var matchCount = await _templateRepository.GetCountAsync(new PrintTemplatePageQuery() { PageIndex = 1, PageSize = 1, Name = dto.Name, ExclusionId = dto.Id });

            if (matchCount > 0)
                throw new UserFriendlyException($"模板名称：{dto.Name}已存在", "100000");

            var template = await _templateRepository.GetAsync(dto.Id);

            if (template == null)
                throw new UserFriendlyException($"模板：{dto.Id}不存在已存在", "100000");

            var oldTemplate = ObjectMapper.Map<PrintTemplate, PrintTemplateDto>(template);

            if (dto.Name != template.Name)
                template.ChangeName(dto.Name);

            template.ChangeFile(dto.TemplateFileId, dto.ImageFileId);

            template = await _templateRepository.UpdateAsync(template);

            var result = ObjectMapper.Map<PrintTemplate, PrintTemplateDto>(template);

            await _operationLogManager.LogAsync(ModuleCodeType.PrintTemplate, Enums.OperationType.Update, oldTemplate, result);

            await LoadFileInfoAsync(new List<PrintTemplateDto>() { result });

            return result;
        }

        public async Task<bool> DeleteAsync(Guid id)
        {
            var template = await _templateRepository.GetAsync(id);

            if (template == null)
                throw new UserFriendlyException($"模板：{id}不存在已存在", "100000");

            await _templateRepository.DeleteAsync(template);

            await _operationLogManager.LogAsync(ModuleCodeType.PrintTemplate, Enums.OperationType.Delete, template, null);

            return true;
        }

        #region
        private async Task LoadFileInfoAsync(List<PrintTemplateDto> templates)
        {
            var fileIds = templates.Select(x => x.TemplateFileId).ToList();

            fileIds.AddRange(templates.Where(x => x.ImageFileId.HasValue).Select(x => x.ImageFileId.Value).ToList());

            var files = await _fileRepository.FindAsync(new PageQuery() { PageIndex = 1, PageSize = int.MaxValue, Ids = fileIds });

            foreach (var template in templates)
            {
                var matchFile = files.FirstOrDefault(x => x.Id == template.TemplateFileId);

                template.TemplateFileName = matchFile?.FileName + matchFile?.FileExtension;
                template.TemplateFileContentType = matchFile?.ContentType;

                var matchImageFile = files.FirstOrDefault(x => x.Id == template.ImageFileId);

                template.ImageFileName = matchImageFile?.FileName + matchImageFile?.FileExtension;
                template.ImageFileContentType = matchImageFile?.ContentType;
            }
        }
        #endregion
    }
}
